home *** CD-ROM | disk | FTP | other *** search
/ HPAVC / HPAVC CD-ROM.iso / TUTORC.ZIP / TCCFILES.ZIP / TUTSBSTC.C < prev    next >
C/C++ Source or Header  |  1994-10-30  |  15KB  |  576 lines

  1. /*
  2.   tutsbstc.c
  3.   Version for Turbo C
  4.   10/30/94 
  5.   SCP
  6.   Adapted from tutprog4.pas, translated into C.
  7.   This version is to go with wormietc.c, a version of the wormie
  8.   program for Turbo C. 
  9.   This version of tutsubs is not as complete as the Microsoft C version,
  10.   because I did most of my work with the MS version, this is just here
  11.   as an example of how to convert to Turbo C.
  12.   All the other examples are for Microsoft C.
  13.   Steve Pinault scp@ohm.att.com
  14. */
  15.  
  16. #include <stdio.h>
  17. #include <stdlib.h>
  18. #include <dos.h>
  19. #include <math.h>
  20. #include <conio.h>
  21. #include <graphics.h>
  22. #include <bios.h>
  23. #include <string.h> 
  24. #include "tcheadex.h"
  25.  
  26.  
  27. //DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  28. //Procedure SetMCGA;  { This procedure gets you into 320x200x256 mode. }
  29. void SetMCGA()
  30. {
  31.   asm {
  32.      mov        ax,0013h
  33.      int        10h
  34.   }
  35. }
  36.  
  37.  
  38. //DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  39. //Procedure SetText;  { This procedure returns you to text mode.  }
  40. void SetText()
  41. {
  42.   asm {
  43.      mov        ax,0003h
  44.      int        10h
  45.   }
  46. }
  47.  
  48.  
  49. //{DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  50. //procedure WaitRetrace; assembler;
  51. /*
  52.     This waits until you are in a Verticle Retrace ... this means that all
  53.     screen manipulation you do only appears on screen in the next verticle
  54.     retrace ... this removes most of the "fuzz" that you see on the screen
  55.     when changing the pallette. It unfortunately slows down your program
  56.     by "synching" your program with your monitor card ... it does mean
  57.     that the program will run at almost the same speed on different
  58.     speeds of computers which have similar monitors. In our SilkyDemo,
  59.     we used a WaitRetrace, and it therefore runs at the same (fairly
  60.     fast) speed when Turbo is on or off. 
  61. */
  62.  
  63. void WaitRetrace()
  64. {
  65.   asm  mov dx,3DAh
  66. l1:
  67.  asm   in al,dx
  68.  asm   and al,08h
  69.  asm   jnz l1
  70. l2:
  71.  asm   in al,dx
  72.  asm   and al,08h
  73.  asm   jz  l2
  74. }
  75.  
  76.  
  77. //DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  78. //Procedure GetPal(ColorNo : Byte; Var R,G,B : Byte);
  79. void GetPal(char ColorNo, char* R, char* G, char* B)
  80. //  This reads the values of the Red, Green and Blue values of a certain
  81. //  color and returns them to you. 
  82. {
  83.    outportb(0x3c7,ColorNo);
  84.    *R=inp(0x3c9);
  85.    *G=inp(0x3c9);
  86.    *B=inp(0x3c9);
  87. }
  88.  
  89.  
  90. //DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  91. //Procedure Pal(ColorNo : Byte; R,G,B : Byte);
  92. void Pal(char ColorNo, char R, char G, char B)
  93. //  This sets the Red, Green and Blue values of a certain color 
  94. {
  95.    outportb(0x3c8,ColorNo);
  96.    outportb(0x3c9,R);
  97.    outportb(0x3c9,G);
  98.    outportb(0x3c9,B);
  99. }
  100.  
  101.  
  102. //DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  103. //Procedure PutPixel (X,Y : Integer; Col : Byte);
  104. //  This puts a pixel on the screen by writing directly to memory. 
  105. void PutPixel(int X, int Y, char Color, int Where)
  106. {
  107.   unsigned char far* VGAScreenPtr;
  108.   unsigned int offset;
  109.   //  VGAScreenPtr=MK_FP(Where,(unsigned)(X+(Y*320)));
  110.   offset=(unsigned)X + (unsigned)(Y<<8) + (unsigned)(Y<<6);
  111.   VGAScreenPtr=MK_FP(Where,offset);
  112.   *VGAScreenPtr=Color;
  113. }
  114.  
  115. ////////////////////////// line //////////////////////////////////
  116. //  Procedure line(a,b,c,d,col:integer);
  117. //  This draws a line from a,b to c,d of color col. }
  118.  
  119.     void Line(int x1, int y1, int x2, int y2, unsigned char Color)
  120.  
  121. //////////////////////////////////////////////////////////////////
  122. {
  123.   int dx,dy,incr1,incr2,d,x,y,xend,yend,yinc,xinc;
  124.  
  125.   dx=abs(x2-x1);
  126.   dy=abs(y2-y1);
  127.  
  128.   if(dx>=dy) // slope < 1
  129.   {
  130.     if(x1>x2)
  131.     {
  132.       x=x2; y=y2; xend=x1;
  133.       if(dy==0) yinc=0;
  134.       else { if(y2>y1) yinc=-1; else yinc=1;}
  135.     }
  136.     else
  137.     {
  138.       x=x1; y=y1; xend=x2;
  139.       if(dy==0) yinc=0;
  140.       else { if(y2>y1) yinc=1; else yinc=-1;}
  141.     }
  142.     incr1=2*dy; d=incr1-dx; incr2=2*(dy-dx);
  143.     PutPixel(x,y,Color,VGA);
  144.     while(x<xend)
  145.     {
  146.       x++;
  147.       if(d<0) d+=incr1;
  148.       else { y+=yinc; d+=incr2;}
  149.       PutPixel(x,y,Color,VGA);
  150.     }
  151.   }
  152.   else
  153.   {
  154.     if(y1>y2)
  155.     { 
  156.       x=x2; y=y2; yend=y1;
  157.       if(dx==0) xinc=0;
  158.       else { if(x2>x1) xinc = -1; else xinc = 1;}
  159.     }
  160.     else
  161.     {
  162.       x=x1; y=y1; yend=y2;
  163.       if(dx==0) xinc=0;
  164.       else { if(x2>x1) xinc=1; else xinc = -1;}
  165.     }
  166.     incr1=2*dx; d=incr1-dy; incr2=2*(dx-dy);
  167.     PutPixel(x,y,Color,VGA);
  168.     while(y<yend)
  169.     {
  170.       y++;
  171.       if(d<0) d+=incr1;
  172.       else { x+=xinc; d+=incr2; }
  173.       PutPixel(x,y,Color,VGA);
  174.     }
  175.   }
  176. }
  177. //////////////////////////////////////////////////////////////////
  178.  
  179.     void Line2(int x1, int y1, int x2, int y2, unsigned char Color, int where)
  180.  
  181. //////////////////////////////////////////////////////////////////
  182. {
  183.   int dx,dy,incr1,incr2,d,x,y,xend,yend,yinc,xinc;
  184.  
  185.   dx=abs(x2-x1);
  186.   dy=abs(y2-y1);
  187.  
  188.   if(dx>=dy) // slope < 1
  189.   {
  190.     if(x1>x2)
  191.     {
  192.       x=x2; y=y2; xend=x1;
  193.       if(dy==0) yinc=0;
  194.       else { if(y2>y1) yinc=-1; else yinc=1;}
  195.     }
  196.     else
  197.     {
  198.       x=x1; y=y1; xend=x2;
  199.       if(dy==0) yinc=0;
  200.       else { if(y2>y1) yinc=1; else yinc=-1;}
  201.     }
  202.     incr1=2*dy; d=incr1-dx; incr2=2*(dy-dx);
  203.     PutPixel(x,y,Color,where);
  204.     while(x<xend)
  205.     {
  206.       x++;
  207.       if(d<0) d+=incr1;
  208.       else { y+=yinc; d+=incr2;}
  209.       PutPixel(x,y,Color,where);
  210.     }
  211.   }
  212.   else
  213.   {
  214.     if(y1>y2)
  215.     { 
  216.       x=x2; y=y2; yend=y1;
  217.       if(dx==0) xinc=0;
  218.       else { if(x2>x1) xinc = -1; else xinc = 1;}
  219.     }
  220.     else
  221.     {
  222.       x=x1; y=y1; yend=y2;
  223.       if(dx==0) xinc=0;
  224.       else { if(x2>x1) xinc=1; else xinc = -1;}
  225.     }
  226.     incr1=2*dx; d=incr1-dy; incr2=2*(dx-dy);
  227.     PutPixel(x,y,Color,where);
  228.     while(y<yend)
  229.     {
  230.       y++;
  231.       if(d<0) d+=incr1;
  232.       else { x+=xinc; d+=incr2; }
  233.       PutPixel(x,y,Color,where);
  234.     }
  235.   }
  236. }
  237.  
  238.  
  239. ////////////////////////// Funny_Line //////////////////////////////////
  240. //  Procedure line(a,b,c,d,col:integer);
  241. //  This draws a line from a,b to c,d of color col. }
  242.  
  243.     void Funny_Line(int x1, int y1, int x2, int y2, int where)
  244.  
  245. //////////////////////////////////////////////////////////////////
  246. {
  247.   int dx,dy,incr1,incr2,d,x,y,xend,yend,yinc,xinc;
  248.   int count = 50;
  249.  
  250.   dx=abs(x2-x1);
  251.   dy=abs(y2-y1);
  252.  
  253.   if(dx>=dy) // slope < 1
  254.   {
  255.     if(x1>x2)
  256.     {
  257.       x=x2; y=y2; xend=x1;
  258.       if(dy==0) yinc=0;
  259.       else { if(y2>y1) yinc=-1; else yinc=1;}
  260.     }
  261.     else
  262.     {
  263.       x=x1; y=y1; xend=x2;
  264.       if(dy==0) yinc=0;
  265.       else { if(y2>y1) yinc=1; else yinc=-1;}
  266.     }
  267.     incr1=2*dy; d=incr1-dx; incr2=2*(dy-dx);
  268.     PutPixel(x,y,(char)count,where);
  269.     count++;
  270.     if(count==101)count=50;
  271.     while(x<xend)
  272.     {
  273.       x++;
  274.       if(d<0) d+=incr1;
  275.       else { y+=yinc; d+=incr2;}
  276.       PutPixel(x,y,(char)count,where);
  277.       count++;
  278.       if(count==101)count=50;
  279.     }
  280.   }
  281.   else
  282.   {
  283.     if(y1>y2)
  284.     { 
  285.       x=x2; y=y2; yend=y1;
  286.       if(dx==0) xinc=0;
  287.       else { if(x2>x1) xinc = -1; else xinc = 1;}
  288.     }
  289.     else
  290.     {
  291.       x=x1; y=y1; yend=y2;
  292.       if(dx==0) xinc=0;
  293.       else { if(x2>x1) xinc=1; else xinc = -1;}
  294.     }
  295.     incr1=2*dx; d=incr1-dy; incr2=2*(dx-dy);
  296.     PutPixel(x,y,(char)count,where);
  297.     count++;
  298.     if(count==101)count=50;
  299.     while(y<yend)
  300.     {
  301.       y++;
  302.       if(d<0) d+=incr1;
  303.       else { x+=xinc; d+=incr2; }
  304.       PutPixel(x,y,(char)count,where);
  305.       count++;
  306.       if(count==101)count=50;
  307.     }
  308.   }
  309. }
  310. // {DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  311. // Procedure PalPlay;
  312. void PalPlay()
  313. {
  314. //  This procedure mucks about with our "virtual pallette", then shoves it
  315. //  to screen. 
  316.     char Tmp[3];
  317. //  This is used as a "temporary color" in our pallette }
  318.     int i,loop1;
  319.  
  320. // This copies color 200 from our virtual pallette to the Tmp variable:
  321.    Tmp[0]=Pall[200][0];
  322.    Tmp[1]=Pall[200][1];
  323.    Tmp[2]=Pall[200][2];
  324.  
  325. // This moves the entire virtual pallette up one color:
  326.    for(i=200;i>0;i--)
  327.    {
  328.      Pall[i][0]=Pall[i-1][0];
  329.      Pall[i][1]=Pall[i-1][1];
  330.      Pall[i][2]=Pall[i-1][2];
  331.    }
  332.  
  333. // This copies the Tmp variable to the bottom of the virtual pallette:
  334.    Pall[0][0]=Tmp[0];
  335.    Pall[0][1]=Tmp[1];
  336.    Pall[0][2]=Tmp[2];
  337.    WaitRetrace();
  338.    for(loop1=1;loop1<256;loop1++)
  339.      Pal((unsigned char)loop1,Pall[loop1][0],Pall[loop1][1],Pall[loop1][2]);
  340. }
  341.  
  342. //////////////////////////////////////////////////////////////////////
  343. // More general purpose version of the above routine, used in tut7.c:
  344. // Moves all colors up one. Note fmemmove is (dest,src)
  345.  
  346. void rotatepal(char locpal[][3], int start, int end)
  347. {
  348.    char Tmp[3];
  349.    int loop1;
  350.    int number=end-start;
  351.  
  352.    _fmemmove(Tmp,locpal[end],3);
  353.    _fmemmove(locpal[start+1],locpal[start],number*3);
  354.    _fmemmove(locpal[start],Tmp,3);
  355.    WaitRetrace();
  356.    for(loop1=start;loop1<end+1;loop1++)
  357.      Pal((unsigned char)loop1,locpal[loop1][0],locpal[loop1][1],
  358.                               locpal[loop1][2]);
  359. }
  360.  
  361.  
  362. // DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  363. // Procedure GrabPallette;
  364. void GrabPallette()
  365. {
  366.   int loop1;
  367.   for(loop1=0;loop1<256;loop1++)
  368.   {
  369.     GetPal((unsigned char)loop1,&Pall2[loop1][0],&Pall2[loop1][1],&Pall2[loop1][2]);
  370.   }
  371. }
  372.  
  373. // DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  374. // Procedure Blackout;
  375. //  This procedure blackens the screen by setting the pallette values of
  376. //  all the colors to zero. 
  377. void Blackout()
  378. {
  379.   int loop1;
  380.   WaitRetrace();
  381.   for(loop1=0;loop1<256;loop1++)
  382.   {
  383.     Pal((unsigned char)loop1,0,0,0);
  384.   }
  385. }
  386.  
  387. // DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  388. // Procedure Fadeup;
  389. // This procedure slowly fades up the new screen }
  390. void FadeUp()
  391. {
  392.   int loop1,loop2;
  393.   char Tmp[3]; // This is temporary storage for the values of a color 
  394.  
  395.   // A color value for Red, green or blue is 0 to 63, so this loop only
  396.   // need be executed a maximum of 64 times:
  397.   for(loop1=0;loop1<64;loop1++)
  398.   {
  399.     WaitRetrace();
  400.     for(loop2=0;loop2<256;loop2++)
  401.     {
  402.       GetPal((unsigned char)loop2,&Tmp[0],&Tmp[1],&Tmp[2]);
  403.       // If the Red, Green or Blue values of color loop2 are less then they
  404.       // should be, increase them by one: 
  405.       if(Tmp[0]<Pall2[loop2][0]) Tmp[0]++;
  406.       if(Tmp[1]<Pall2[loop2][1]) Tmp[1]++;
  407.       if(Tmp[2]<Pall2[loop2][2]) Tmp[2]++;
  408.       // Set the new, altered pallette color: 
  409.       Pal((unsigned char)loop2,Tmp[0],Tmp[1],Tmp[2]);
  410.     }
  411.   }
  412. }
  413.  
  414. // DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  415. // Procedure FadeDown;
  416. // This procedure fades the screen out to black. }
  417. void FadeDown()
  418. {
  419.   int loop1,loop2;
  420.   char Tmp[3]; // This is temporary storage for the values of a color 
  421.  
  422.   // A color value for Red, green or blue is 0 to 63, so this loop only
  423.   // need be executed a maximum of 64 times:
  424.   for(loop1=0;loop1<64;loop1++)
  425.   {
  426.     WaitRetrace();
  427.     for(loop2=0;loop2<256;loop2++)
  428.     {
  429.       GetPal((unsigned char)loop2,&Tmp[0],&Tmp[1],&Tmp[2]);
  430.       // If the Red, Green or Blue values of color loop2 are not yet zero,
  431.       // then, decrease them by one. }
  432.       if(Tmp[0]>0) Tmp[0]--;
  433.       if(Tmp[1]>0) Tmp[1]--;
  434.       if(Tmp[2]>0) Tmp[2]--;
  435.       // Set the new, altered pallette color: 
  436.       Pal((unsigned char)loop2,Tmp[0],Tmp[1],Tmp[2]);
  437.     }
  438.   }
  439. }
  440.  
  441. // DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  442. // Procedure RestorePallette;
  443. // This procedure restores the origional pallette 
  444. void RestorePallette()
  445. {
  446.   int loop1;
  447.   WaitRetrace();
  448.   for(loop1=0;loop1<256;loop1++)
  449.     Pal ((unsigned char)loop1,Pall2[loop1][0],Pall2[loop1][1],Pall2[loop1][2]);
  450. }
  451.  
  452. ///////////////////////////////////////////////////////////////////////////////
  453.  
  454. // {DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  455. // Procedure Cls (Col : Byte; Where:Word);
  456. // This clears the screen to the specified color, on the VGA or on the
  457. // virtual screen 
  458. // Argument Where will be either VGA or Vaddr: the SEG of the Screen Pointer.
  459. void Cls(char Color, int Where)
  460. {
  461. //Fillchar (Mem [where:0],64000,col);
  462.   unsigned char far* ScreenPtr;
  463.   ScreenPtr=MK_FP(Where,0x0);
  464.   _fmemset(ScreenPtr,Color,(unsigned int)64000);
  465. }
  466.  
  467. // {DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  468. // Procedure Flip;
  469. // { This flips the virtual screen to the VGA screen. }
  470. void Flip()
  471. {
  472.   unsigned char far* ScreenPtr;
  473.   ScreenPtr=MK_FP(VGA,0x0);
  474.   _fmemmove(ScreenPtr,VirtPtr,(unsigned int)64000);
  475. }
  476.  
  477. // {DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  478. // procedure flip(source,dest:Word);
  479. //   { This copies the entire screen at "source" to destination }
  480. void Flip2(int Source, int Dest)
  481. {
  482.   asm {
  483.     push    ds
  484.     mov     ax, Dest
  485.     mov     es, ax
  486.     mov     ax, Source
  487.     mov     ds, ax
  488.     xor     si, si
  489.     xor     di, di
  490.     mov     cx, 32000
  491.     rep     movsw
  492.     pop     ds
  493.   }
  494. }
  495.  
  496. //int random(int x)
  497. //{
  498. //  return (int)((long)(rand()*(long)x)/(long)32767);
  499. //}
  500.  
  501. // DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD
  502. // Function rad (theta : real) : real;
  503. // This calculates the degrees of an angle
  504. //   rad := theta * pi / 180
  505. float rad(float theta)
  506. {
  507.   return theta*PI/(float)180.0;
  508. }
  509.  
  510. int round(float x)
  511. {
  512.   if(x>=0)
  513.     return (int)(x+0.5);
  514.   else
  515.     return (int)(x-0.5);
  516. }
  517.  
  518. ////////////////  SetUpVirtual /////////////////////////
  519. // Sets up pointers to 2 virtual screens
  520.  
  521. void SetUpVirtual()
  522. {
  523.   VirtPtr=&Virtual[0];
  524.   Vaddr = FP_SEG(VirtPtr);
  525.   VirtPtr=&Virtual2[0];
  526.   Vaddr2 = FP_SEG(VirtPtr);
  527. }
  528.  
  529. //{DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  530. //Procedure Hline (x1,x2,y:word;col:byte;where:word); assembler;
  531. //  { This draws a horizontal line from x1 to x2 on line y in color col }
  532. void Hline(int x1, int x2, int y, char col, int where)
  533. {
  534.   asm mov   ax,where
  535.   asm mov   es,ax
  536.   asm mov   ax,y
  537.   asm mov   di,ax
  538.   asm shl   ax,8
  539.   asm shl   di,6
  540.   asm add   di,ax
  541.   asm add   di,x1
  542.  
  543.   asm mov   al,col
  544.   asm mov   ah,al
  545.   asm mov   cx,x2
  546.   asm sub   cx,x1
  547.   asm shr   cx,1
  548.   asm jnc   lstart
  549.   asm stosb
  550. lstart :
  551.   asm rep   stosw
  552. }
  553.  
  554. // {DDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDDD}
  555. // Procedure Putpixel (X,Y : Integer; Col : Byte; where:word);
  556. // This puts a pixel on the screen by writing directly to memory. }
  557. // Assembly version
  558. void PutPixel2(int x, int y, char col, int where)
  559. {
  560.   asm {
  561.     mov     ax,where
  562.     mov     es,ax
  563.     mov     bx,x
  564.     mov     dx,y
  565.     mov     di,bx
  566.     mov     bx, dx   //               {; bx = dx}
  567.     shl     dx, 8
  568.     shl     bx, 6
  569.     add     dx, bx   //               {; dx = dx + bx (ie y*320)}
  570.     add     di, dx   //               {; finalise location}
  571.     mov     al, col
  572.     stosb
  573.   }
  574. }    
  575.  
  576.